home *** CD-ROM | disk | FTP | other *** search
- // main2.cpp
- // A demonstration of a database buffer
- // made simpler by smart pointers.
-
- #define DEBUG
-
- #include "anyclass.hpp"
-
- class BufferedDatabase
- {
- public:
- BufferedDatabase (void){};
- ~BufferedDatabase (void);
-
- void getRecPtr (
- int recNum,
- RefCntPtr(anyClass)& ptr);
-
- private:
- enum {bfrSize=3};
-
- RefCntPtr(anyClass) bfr[bfrSize];
-
- // these functions would actually
- // read from the disk DB.
- // for now, we'll just pretend
- void getRecWithNew (
- int recNum,
- RefCntPtr(anyClass)& ptr);
-
- void putRec (
- RefCntPtr(anyClass)& ptr);
- };
-
-
- void BufferedDatabase::getRecPtr (
- int recNum,
- RefCntPtr(anyClass)& ptr)
- {
- // first, see if it is in the buffer
-
- for (int i = 0; i < bfrSize; ++i)
- if ( bfr[i]
- && (bfr[i]->intVal == recNum)
- )
- {
- ptr = bfr[i];
- return;
- };
-
- // if we made it to here, then it
- // is not in the buffer, so get it
- // from disk;
-
- RefCntPtr(anyClass) tmp;
- getRecWithNew (recNum, tmp);
-
- // return if not found
- if (0 == tmp)
- {
- ptr = 0;
- return;
- };
-
- // see if it can be inserted
- // into buffer
- for (i = 0; i < bfrSize; ++i)
- if (0 == bfr[i])
- {
- bfr[i] = tmp;
- ptr = tmp;
- return;
- };
-
- ptr = 0;
-
- // if it didn't return, then there
- // is no space - will have to find
- // some.
- for (i = 0; i < bfrSize; ++i)
-
- // reference count of 1 means the
- // only pointer to this object
- // is bfr[i]. Since nothing
- // outside this routine is pointing
- // to it, we can get rid of it.
-
- if (bfr[i]->refCnt() == 1)
- {
- putRec (bfr[i]);
- bfr[i] = tmp;
- ptr = tmp;
- return;
- };
-
- // if still didn't return,
- // out of space
-
- cout << "BUFFER FULL\n\n";
- // obviously, running out of space
- // is a bad thing - a real-world
- // scheme wouldn't use as array,
- // but some form of dynamic
- // allocation
-
- };
-
-
- void BufferedDatabase::getRecWithNew (
- int recNum,
- RefCntPtr(anyClass)& ptr)
- {
- // would get record from database
- // again, we'll just fake it
-
- // pretend that records 1000
- // and above don't exist
-
- if (recNum >= 1000)
- {
- ptr = 0;
- return;
- };
-
- ptr = new anyClass;
-
- // pretend that it's
- // getting a record from disk
- ptr->intVal = recNum;
- ptr->string = "something";
-
- cout << "getting from disk - rec # "
- << ptr->intVal << "\n\n";
- };
-
-
- void BufferedDatabase::putRec (
- RefCntPtr(anyClass)& ptr)
- {
- cout << "putting to disk - rec # "
- << ptr->intVal << "\n\n";
- };
-
-
- BufferedDatabase::~BufferedDatabase(void)
- {
- for (int i = 0; i < bfrSize; ++i)
- if (bfr[i])
- {
- putRec (bfr[i]);
- bfr[i] = 0;
- };
- };
-
-
- void main (void)
- {
- cout << "start of main\n\n";
- BufferedDatabase db;
-
- RefCntPtr(anyClass) ptrA, ptrB,
- ptrC, ptrD;
-
- db.getRecPtr (1, ptrA);
- ptrA->show();
-
- db.getRecPtr (2, ptrA);
- db.getRecPtr (3, ptrA);
- db.getRecPtr (4, ptrA);
-
- db.getRecPtr (2, ptrA);
- db.getRecPtr (3, ptrB);
- db.getRecPtr (4, ptrC);
- db.getRecPtr (5, ptrD);
- if (!ptrD)
- cout << "getRecFailed\n\n";
-
- db.getRecPtr (1005, ptrD);
- ptrD->show();//an error
-
- cout << "end of main\n\n";
- };
-